from fastapi import APIRouter, HTTPException
from pydantic import BaseModel
from typing import List, Optional, Dict
from backtest_single import run_backtest
import pandas as pd

router = APIRouter(
    prefix="/api/backtest",
    tags=["Backtest"]
)

class BacktestRequest(BaseModel):
    stock_code: str
    start_date: str
    end_date: str
    initial_cash: float

class TransactionRecord(BaseModel):
    date: str
    type: str
    stock_code: str
    price: float
    shares: int
    amount: float
    cash_after_transaction: float
    shares_after_transaction: int

class PortfolioHistoryRecord(BaseModel):
    date: str
    portfolio_value: float
    cash: float
    shares_held: int
    stock_price: float

class CurrentHolding(BaseModel):
    stock_code: str
    shares: int
    buy_price: float
    buy_date: str
    current_price: Optional[float]
    unrealized_pnl: Optional[float]

class BacktestSummary(BaseModel):
    stock_code: str
    start_date: str
    end_date: str
    initial_cash: float
    final_cash: float
    final_shares_held: int
    final_portfolio_value: float

class BacktestResponse(BaseModel):
    message: str
    transactions: List[TransactionRecord]
    portfolio_history: List[PortfolioHistoryRecord]
    current_holdings: List[CurrentHolding]
    summary: BacktestSummary
    error: Optional[str] = None

@router.post("/run", response_model=BacktestResponse)
async def run_backtest_api(request: BacktestRequest):
    try:
        results = run_backtest(
            stock_code=request.stock_code,
            start_date=request.start_date,
            end_date=request.end_date,
            initial_cash=request.initial_cash
        )
        if "error" in results.get("summary", {}):
            raise HTTPException(status_code=500, detail=results["summary"]["error"])
        if "message" in results.get("summary", {}):
            return BacktestResponse(
                message=results["summary"]["message"],
                transactions=[],
                portfolio_history=[],
                current_holdings=[],
                summary=BacktestSummary(
                    stock_code=request.stock_code,
                    start_date=request.start_date,
                    end_date=request.end_date,
                    initial_cash=request.initial_cash,
                    final_cash=request.initial_cash,
                    final_shares_held=0,
                    final_portfolio_value=request.initial_cash,
                )
            )
        return BacktestResponse(
            message="Backtest completed successfully.",
            transactions=[TransactionRecord(**t) for t in results["transactions"]],
            portfolio_history=[PortfolioHistoryRecord(**p) for p in results["portfolio_history"]],
            current_holdings=[],
            summary=BacktestSummary(**results["summary"])
        )
    except HTTPException as http_exc:
        raise http_exc
    except Exception as e:
        raise HTTPException(status_code=500, detail=f"Backtest failed: {str(e)}")